<script setup lang="ts">
import { PropType } from "vue";

type VideoData = {
  src: string;
  type?: string;
};

const props = defineProps({
  videoData: {
    required: true,
    type: Array as PropType<Array<VideoData>>,
    default: () => [],
  },
});

// 视频标签ref
const VideoRef = ref<HTMLVideoElement>();
const curVideoDom = ref<HTMLVideoElement>();
// 视频容器观察器
const containerOb = ref<IntersectionObserver>();
// 是否为第一次进入视口
const first = ref<boolean>(false);
// 当前播放视频
const curIndex = ref<number>(0);

// 视频进度
const currentTime = ref<number>(0);

onMounted(() => {
  first.value = false;
  // 获取视频容器
  const container = document.querySelector(
    ".video-swiper-container"
  ) as HTMLElement;
  containerOb.value = new IntersectionObserver(
    (entries: IntersectionObserverEntry[]) => {
      entries.forEach((item) => {
        // 进入视口范围
        if (item.isIntersecting && !first.value) {
          // 视频开始播放
          createVideo();
          first.value = true;
          console.log("轮播视频组件进入视口范围，开始播放");
        }
      });
    }
  );
  // 开始监听
  containerOb.value?.observe(container);
});

onBeforeUnmount(() => {
  // 移除video事件监听
  curVideoDom.value?.removeEventListener("timeupdate", timeupdate);
  curVideoDom.value?.removeEventListener("ended", ended);
});

// 点击切换视频
const handleSwitchVideo = (index: number) => {
  if(curIndex.value == index) return;
  pause();
  setVideo(index);
}

function createVideo() {
  nextTick(() => {
    // 获取当前处于播放的video标签
    curVideoDom.value = document.querySelector(
      ".video-wrap .active"
    ) as HTMLVideoElement;
    
    // 开始播放
    curVideoDom.value?.play();
    // 监听播放进度
    curVideoDom.value?.addEventListener("timeupdate", timeupdate);
    // 监听自然播放结束
    curVideoDom.value?.addEventListener("ended", ended);
  });
}

// 暂停播放
function pause() {
  curVideoDom.value?.pause();
}

// 下一个视频
function next() {
  const index =
    curIndex.value >= props.videoData.length - 1 ? 0 : curIndex.value + 1;
  setVideo(index);
}

// 设置视频切换
function setVideo(index: number) {
  curIndex.value = index;
  // 重置进度条
  reset();
  
  // 下一个视频开始播放
  createVideo();
  // console.log("下一个视频index==>", curIndex.value);
}

/**
 * 监听播放进度
 */
function timeupdate() {
  currentTime.value =
    (curVideoDom.value!.currentTime / curVideoDom.value!.duration) * 100 || 0;
  // console.log('当前视频播放进度==>', currentTime.value);
}

/**
 * 监听自然播放结束
 */
function ended() {
  next();
  // console.log("视频自然播放结束事件");
}

// 重置
function reset() {
  currentTime.value = 0;
  curVideoDom.value!.currentTime = 0;
}

defineOptions({
  name: "VideoSwiper",
});
</script>

<template>
  <div class="video-swiper-container" v-if="videoData.length">
    <div class="video-wrap">
      <video
        ref="VideoRef"
        muted
        v-for="(video, index) in videoData"
        :key="index"
        :class="{ active: curIndex == index }"
      >
        <source :src="video.src" :type="video.type || 'video/mp4'" />
      </video>
    </div>

    <!-- 进度块 -->
    <div class="progress-wrap flex items-center justify-center">
      <el-progress
        class="progress cursor-pointer"
        v-for="(video, i) in videoData"
        :key="video.src"
        :percentage="i == curIndex ? currentTime : 0"
        status="warning"
        :stroke-width="4"
        :show-text="false"
        @click="handleSwitchVideo(i)"
      />
    </div>
  </div>
</template>

<style lang="scss" scoped>
.video-wrap {
  position: relative;
  z-index: 2;
  width: 411px;
  height: 647px;
  video {
    position: absolute;
    width: 100%;
    height: 100%;
    opacity: 0;
    transition: opacity 0.3s;
    mix-blend-mode: darken;
  }
}

.progress-wrap {
  position: absolute;
  bottom: 20px;
  left: 8px;
  width: 234px;
  z-index: 2;
}

// 进度条样式深层穿透
:deep(.progress-wrap) {
  .progress {
    width: 40px;
    padding: 0 5px;
  }
}

// 当前处于显示的video
.active {
  opacity: 1 !important;
}
</style>
